home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Gekkan Dennou Club 147
/
Gekkan Dennou Club - 2000.8 Vol. 147 (Japan).7z
/
Gekkan Dennou Club - 2000.8 Vol. 147 (Japan) (Track 1).bin
/
games
/
ippon
/
source.lzh
/
player.c
< prev
next >
Wrap
C/C++ Source or Header
|
2000-07-07
|
10KB
|
401 lines
/* player.c */
#include <sys/iocs.h>
#include <xsp2lib.h>
#include "main.h"
#include "player.h"
#include "shot.h"
#include "eshot.h"
#include "effect.h"
#include "txfont.h"
#include "sound.h"
#define PLAYER_BANK1 8 /* 少し傾きパターンへ移行するまでの値 */
#define PLAYER_BANK2 12 /* 一番傾きパターンへ以下同文 */
#define PLAYER_SPEED 15 /* 自機の速度 */
#define PLAYER_PALET 0x0500 /* 自機のパレット */
#define PLAYER_PALET_FLASH 0x0D00
#define PLAYER_START_X 144 /* 自機出現時の座標 */
#define PLAYER_START_Y (256+32)
#define PLAYER_MINX (16+8) /* X 座標最小値 */
#define PLAYER_MAXX (16+255-8)
#define PLAYER_MINY (16+16) /* Y 座標最小値 */
#define PLAYER_MAXY (16+255-12)
#define TIME_MUTEKI 150 /* 登場時の無敵時間 */
enum {
PLAYER_PT_RIGHT2 = 0, /* 自機が一番右に傾いている時のパターン */
PLAYER_PT_RIGHT1, /* 〃 少し右に 〃 */
PLAYER_PT_CENTER, /* 〃 正面を向いている時のパターン */
PLAYER_PT_LEFT1, /* 自機が少し右に傾いている時のパターン */
PLAYER_PT_LEFT2 /* 〃 一番右に 〃 */
};
/* 残機を表示 */
void DispRest (void)
{
short h;
#define REST_DISP_X 2
#define REST_DISP_Y 1
TxfontCursor (REST_DISP_X, REST_DISP_Y);
for (h = 0; h < 10; h++) {
if (h < player->rest - 1)
TxfontPutchar ('i'); /* 'i' に自機のマークが割り当てられてます */
else
TxfontPutchar (' ');
};
}
/* ゲーム開始時に呼ばれる */
void PlayerInit (void)
{
}
/* プレイヤー出現時に呼ばれる */
void PlayerAlloc (void)
{
player->lx = PLAYER_START_X * 65536;
player->ly = PLAYER_START_Y * 65536;
player->status = PLAYER_STATUS_APPEAR; /* 出現状態へ */
player->counter = 0;
player->muteki = TIME_MUTEKI;
player->flash = 0;
player->game_over = GAME_PLAY;
/* コア関連 */
player->core_info = PALET_CORE_BLUE | PRIORITY_PLAYER;
player->core_pt = sp_core + 1;
}
/* 自機が生きている時の移動処理 */
static void PlayerMoveAlive (void)
{
int j; /* ジョイスティックの入力 */
j = _iocs_joyget (0); /* ジョイスティック0番 */
#if 0
/* [A] ボタンが押されたか? */
if ((j & 0b00100000) == 0)
player->game_over = GAME_ABORT; /* ゲームオーバーに */
#endif
/* [B] ボタンが押されたか? */
if ((j & 0b1000000) == 0)
ShotAlloc ();
/* 自機の上下移動処理 */
switch (j & 0b0011) {
case 0b0010: /* 上 */
if (player->ly >> 16 > PLAYER_MINY)
player->ly += xytable[PLAYER_SPEED][192].y;
break;
case 0b0001: /* 下 */
if (player->ly >> 16 < PLAYER_MAXY)
player->ly += xytable[PLAYER_SPEED][64].y;
break;
default: /* それ以外 */
break;
}
/* 自機の左右移動処理+左右傾き処理 */
switch (j & 0b1100) {
case 0b1000: /* 左 */
if (player->lx >> 16 > PLAYER_MINX)
player->lx += xytable[PLAYER_SPEED][128].x;
if (player->bank > 0) {
player->bank = 0;
} else {
if (player->bank > -PLAYER_BANK2)
player->bank--;
}
break;
case 0b0100: /* 右 */
if (player->lx >> 16 < PLAYER_MAXX)
player->lx += xytable[PLAYER_SPEED][0].x;
if (player->bank < 0) {
player->bank = 0;
} else {
if (player->bank < PLAYER_BANK2)
player->bank++;
}
break;
default: /* それ以外 */
/* 自機の傾きを元に戻す処理 */
if (player->bank != 0) {
if (player->bank > 0)
player->bank--;
else
player->bank++;
}
break;
}
/* 自機の傾き (player->bank) から自機の複合スプライトNo.を求める */
if (player->bank == 0) {
player->pt = obj_player + PLAYER_PT_CENTER;
} else {
if (player->bank > 0) {
if (player->bank < PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_LEFT1;
else
player->pt = obj_player + PLAYER_PT_LEFT2;
} else {
if (player->bank > -PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_RIGHT1;
else
player->pt = obj_player + PLAYER_PT_RIGHT2;
}
}
player->x = player->lx / 65536;
player->y = player->ly / 65536;
/* 各種キー入力 */
if ((j & 0b1111) == 0) { /* [SELECT]+[START] */
player->game_over = GAME_ABORT;
return;
}
if (_iocs_bitsns (0x0c) & 0b10) {
/* [BREAK] */
while (_iocs_bitsns (0x0c) & 0b10);
player->game_over = GAME_ABORT;
return;
}
/* ポーズ処理 */
if ((_iocs_bitsns (0x00) & 0b10) /* [ESC] */
||((j & 0b1100) == 0)) { /* ゲーム中に [START] */
pause_flag = !0;
while ((_iocs_bitsns (0x00) & 0b10) || ((_iocs_joyget (0) & 0b1100) == 0));
while ((!(_iocs_bitsns (0x00) & 0b10)) && (!((_iocs_joyget (0) & 0b1100) == 0)));
while ((_iocs_bitsns (0x00) & 0b10) || ((_iocs_joyget (0) & 0b1100) == 0));
pause_flag = 0;
}
/* 無敵状態の処理 */
player->info = PLAYER_PALET | PRIORITY_PLAYER;
if (player->muteki) {
player->muteki--;
player->flash++;
if (player->muteki > 55) {
/* バリアが沢山残っているので速いフラッシュ */
if (player->flash > 1) {
player->info = PLAYER_PALET_FLASH | PRIORITY_PLAYER;
player->flash = 0;
}
} else {
/* バリアが少ししかないので遅いフラッシュ */
if (player->flash > 5)
player->info = PLAYER_PALET_FLASH | PRIORITY_PLAYER;
if (player->flash > 10)
player->flash = 0;
}
}
xobj_set_st (player); /* 自機を表示 */
/* コアの表示 */
player->core_x = player->x - 8;
player->core_y = player->y - 8;
xsp_set_st (&(player->core_x));
}
/* 自機が死んだ時の移動処理 */
static void PlayerMoveDead (void)
{
player->x = player->lx / 65536;
player->y = player->ly / 65536;
/* 自機の傾きを元に戻す処理 */
if (player->bank != 0) {
if (player->bank > 0)
player->bank--;
else
player->bank++;
}
/* 自機の傾き (player->bank) から自機の複合スプライトNo.を求める */
if (player->bank == 0) {
player->pt = obj_player + PLAYER_PT_CENTER;
} else {
if (player->bank > 0) {
if (player->bank < PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_LEFT1;
else
player->pt = obj_player + PLAYER_PT_LEFT2;
} else {
if (player->bank > -PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_RIGHT1;
else
player->pt = obj_player + PLAYER_PT_RIGHT2;
}
}
player->info = PLAYER_PALET | PRIORITY_PLAYER;
switch (player->counter++) {
case 0:
/* 今死んだところなら爆発パターンを出す */
EffectAlloc (EFFECT_EXPLPLAYER, 0, player->x, player->y); /* 爆発パターンを出現させる */
SoundSetSE (SE_PLAYER_EXPL); /* プレイヤーの爆発音 */
break;
case 8 * 1:
case 8 * 2:
case 8 * 3:
case 8 * 4:
case 8 * 5:
{
signed short x, y;
x = rndtable[(player->counter) & 0xff ^ 0x55] - 128;
y = rndtable[(player->counter + 1) & 0xff ^ 0xaa] - 128;
/* player->counter は乱数の種として使用しています */
EffectAlloc (EFFECT_EXPLPLAYER, 0, player->x + x / 8, player->y + y / 8);
SoundSetSE (SE_PLAYER_EXPL); /* プレイヤーの爆発音 */
}
break;
case 8 * 7:
/* 最後の「どっかーん」 */
EffectAlloc (EFFECT_EXPLPLAYER, 0, player->x, player->y);
SoundSetSE (SE_EXPL_L);
player->x = 256 + 32;
player->y = 256 + 32;
break;
case 8 * 12:
/* 座標を初期化 */
player->lx = PLAYER_START_X * 65536;
player->ly = PLAYER_START_Y * 65536;
player->status = PLAYER_STATUS_APPEAR; /* 出現状態へ */
player->counter = 0;
player->rest--;
if (player->rest <= 0) {
player->game_over = GAME_OVER;
} else {
if (!eshot_erase)
eshot_erase = ESHOT_ERASE; /* 弾消し */
}
DispRest (); /* 残機数表示 */
break;
default:
if (player->counter < 55) {
xobj_set_st (player); /* 自機を表示 */
/* コアの表示 */
player->core_x = player->x - 8;
player->core_y = player->y - 8;
xsp_set_st (&(player->core_x));
}
break;
}
}
/* 自機が死んだ後の登場処理 */
static void PlayerMoveAppear (void)
{
player->bank = 0;
player->pt = obj_player + PLAYER_PT_CENTER;
player->ly -= (4 * 65536);
player->x = player->lx / 65536;
player->y = player->ly / 65536;
/* 自機がある程度上まで進んだら通常状態へ */
if (player->y < 160) {
player->status = PLAYER_STATUS_ALIVE;
player->muteki = TIME_MUTEKI;
}
player->info = PLAYER_PALET | PRIORITY_PLAYER;
if (player->flash++ > 1) {
player->info = PLAYER_PALET_FLASH | PRIORITY_PLAYER;
player->flash = 0;
}
xobj_set_st (player); /* 自機を表示 */
/* コアの表示 */
player->core_x = player->x - 8;
player->core_y = player->y - 8;
xsp_set_st (&(player->core_x));
}
/* ボスを倒した後の移動処理 */
static void PlayerMoveComplete (void)
{
/* 自機の傾きを元に戻す処理 */
if (player->bank != 0) {
if (player->bank > 0)
player->bank--;
else
player->bank++;
}
/* 自機の傾き (player->bank) から自機の複合スプライトNo.を求める */
if (player->bank == 0) {
player->pt = obj_player + PLAYER_PT_CENTER;
} else {
if (player->bank > 0) {
if (player->bank < PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_LEFT1;
else
player->pt = obj_player + PLAYER_PT_LEFT2;
} else {
if (player->bank > -PLAYER_BANK1)
player->pt = obj_player + PLAYER_PT_RIGHT1;
else
player->pt = obj_player + PLAYER_PT_RIGHT2;
}
}
player->info = PLAYER_PALET | PRIORITY_PLAYER;
player->ly -= (4 * 65536);
player->x = player->lx / 65536;
player->y = player->ly / 65536;
xobj_set_st (player); /* 自機を表示 */
if (player->y < -32)
player->game_over = GAME_COMPLETE2; /* ゲーム終了 */
/* コアの表示 */
player->core_x = player->x - 8;
player->core_y = player->y - 8;
xsp_set_st (&(player->core_x));
}
/* 垂直同期ごとに呼ばれる */
void PlayerMove (void)
{
if ((player->game_over == GAME_COMPLETE)
&& (player->status == PLAYER_STATUS_ALIVE))
player->status = PLAYER_STATUS_COMPLETE;
switch (player->status) {
case PLAYER_STATUS_ALIVE:
PlayerMoveAlive ();
break;
case PLAYER_STATUS_DEAD:
PlayerMoveDead ();
break;
case PLAYER_STATUS_APPEAR:
PlayerMoveAppear ();
break;
case PLAYER_STATUS_COMPLETE:
PlayerMoveComplete ();
break;
}
}